"""
Python中一切都是对象，它们要么是类的实例，要么是元类的实例，除了type。type实际上是它自己的元类
对象可以进行以下操作：
1、你可以将它赋值给一个变量
2、你可以拷贝它
3、你可以为它增加属性
4、你可以将它作为函数参数传递。
"""

class Foo(object):
    bar=True

#Foo = type('Foo',(),{'bar':True})

# class Foochild(Foo):
#     pass
#保用type增加类的方法
def echo_bar(self):
    print(self)
    print(self.bar)

Foochild=type('Foochild',(Foo,),{'echo_bar':echo_bar})

my_lili= Foochild()
print("*********")
my_lili.echo_bar()

"""
你可以在写一个类的时候为其添加metaclass属性。
class Foo(object):
    __metaclass__ = something…
Foo中有metaclass这个属性吗？如果是，Python会在内存中通过metaclass创建一个名字为Foo的类对象。
如果Python没有找到metaclass，它会继续在Bar（父类）中寻找metaclass属性，并尝试做和前面同样的操作。
如果Python在任何父类中都找不到metaclass，它就会在模块层次中去寻找metaclass，并尝试做同样的操作。
如果还是找不到metaclass, Python就会用内置的type来创建这个类对象
    """

#------------------比如将属性全部转化为大写-------------------------------------------------------------------
# 元类会自动将你通常传给‘type’的参数作为自己的参数传入
def upper_attr(future_class_name, future_class_parents, future_class_attr):
    '''返回一个类对象，将属性都转为大写形式'''
    #  选择所有不以'__'开头的属性
    attrs = ((name, value) for name, value in future_class_attr.items() if not name.startswith('__'))
    # 将它们转为大写形式
    uppercase_attr = dict((name.upper(), value) for name, value in attrs)

    # 通过'type'来做类对象的创建
    return type(future_class_name, future_class_parents, uppercase_attr)


__metaclass__ = upper_attr  # 这会作用到这个模块中的所有类


class Foo(object):
    # 我们也可以只在这里定义__metaclass__，这样就只会作用于这个类中
    bar = 'bip'
